package cn.biplam.back.operator.tree;

import java.util.ArrayList;

import cn.biplam.common.bean.md.IndexTable;
import cn.biplam.common.bean.tree.IndexTableSimple;
import cn.biplam.common.client.DataFilter;
import cn.biplam.common.client.Operator;
import cn.biplam.common.client.OperatorResult;
import cn.biplam.common.interfaces.DataOperator;
import cn.biplam.common.opcode.SysManageCode.TreeIndexCode;
import cn.biplam.common.opcode.mdManage.TreeCode.TreeOptCode;
import cn.biplam.common.paramters.TreeParam;
import cn.biplam.common.struc.MdStruc;
import cn.biplam.common.wrapper.ErrorMessage;
import cn.biplam.common.wrapper.tree.TreeIndexFields;

/**
 * 业务对象主题数据操作类
 * @author XiaoRuxing 2009-5-18下午10:31:46
 * @version 1.0
 */
public class OptTree extends DataOperator{
	
	/** 业务对象主题元数据表表名 */
	private static final String tName="noname";
	
	/**
	 * 传入用户ID创建业务对象主题数据操作类
	 * @param userID 用户ID
	 * @throws ErrorMessage
	 */
	public OptTree() throws ErrorMessage {
		super(tName);
	}
	
	/**
	 * 实现类的交换器，根据交换代码执行相应的方法生成并执行SQL语句，返回执行结果
	 * @return 交换代码对应Sql的执行结果
	 * @throws ErrorMessage
	 */
	protected OperatorResult _exchange() throws ErrorMessage {
		ArrayList<String> sql=new ArrayList<String>();
		if(opId.equals(TreeOptCode.Insert)){
			String nodeId = insert(sql, filter);
			filter.setIfGetSql(false);
			OperatorResult or = doing(sql,Operator_Type.DML);
			or.setLastRowId(nodeId);
			return or;
		}else if(opId.equals(TreeOptCode.Delete)){
			delete(sql, filter);
			filter.setIfGetSql(false);
			return doing(sql,Operator_Type.DML);	
		}else if(opId.equals(TreeOptCode.Update)){
			update(sql, filter);
			filter.setIfGetSql(false);
			return doing(sql,Operator_Type.DML);
		}else{
			throw new ErrorMessage("OptTree.java Error,Data Operator id not found:"+ opId+" !");
		}
	}
	
	/**
	 * 插入业务对象模型表主题  
	 * @throws ErrorMessage 
	 */
	private String insert(ArrayList<String> sql,DataFilter filter) throws ErrorMessage{
		ArrayList<String> sqlcust = null;
		ArrayList<String> sqltree = null;
		/** 取额外sql,根据OperatorId*/
		String realId = null;
		String operatorIdAddNew = filter.getValue(TreeParam.OPERATORID_ADD);
		if(operatorIdAddNew!=null && !"".equals(operatorIdAddNew.trim())){
			OperatorResult or = Operator.get(operatorIdAddNew, userId, filter, dbResource, true);
			sqlcust = or.getSqls();
			realId = or.getLastRowId();
		}
		
		/** 获取索引表插入SQL */
		DataFilter treeFilter=_generatorUpdateIndexFilter(filter,"",realId);
		OperatorResult or = Operator.get(TreeIndexCode.Insert_By_Index_Id, userId, treeFilter, dbResource, true);
		sqltree = or.getSqls();
		if(sqlcust!=null){
			sql.addAll(sqlcust);
		}
		if(sqltree!=null){
			sql.addAll(sqltree);;
		}
		return or.getLastRowId();
	}
	
	/**
	 * 更新业务对象主题信息 
	 * @throws ErrorMessage 
	 */
	private void update(ArrayList<String> sql,DataFilter filter) throws ErrorMessage{
		ArrayList<String> sqlcust = null;
		/**取额外的修改sql*/
		String operatorIdModify = filter.getValue(TreeParam.OPERATORID_MODIFY);
		if(operatorIdModify!=null && !"".equals(operatorIdModify.trim())){
			OperatorResult or = Operator.get(operatorIdModify, userId, filter, dbResource, true);
			sqlcust = or.getSqls();
		}
		/**索引表字段对象*/
		String treeTableName=filter.getValue(TreeParam.TABLE_NAME);
		TreeIndexFields treeFields=TreeIndexFields.getTreeFields(treeTableName);
		ArrayList<String> sqlIndex = null;
		/**更新业务对象表在索引表中的记录 */
		IndexTableSimple mIndexTableS = IndexTableSimple.getNewInstance(userId, 
														   treeTableName);
		sqlIndex = mIndexTableS.update(filter.getValue(treeFields.getNodeId()),
									   filter.getValue(TreeParam.NAME),
									   filter.getValue(TreeParam.DESC), 
									   null, true).getSqls();
		if(sqlcust!=null){
			sql.addAll(sqlcust);
		}
		if(sqlIndex!=null){
			sql.addAll(sqlIndex);;
		}
	}
	
	/**
	 * 删除业务对象主题<br>
	 * <ul>需要参数：
	 * <li>主题ID
	 * <li>主题对应的索引表ID
	 * </ul>  
	 * @throws ErrorMessage 如果主题有子主题或者表则不能删除 
	 */
	private void delete(ArrayList<String> sql,DataFilter filter) throws ErrorMessage{
		ArrayList<String> sqlcust = null;
		/**取额外的删除sql*/
		String operatorIdDelete = filter.getValue(TreeParam.OPERATORID_DELETE);
		if(operatorIdDelete!=null && !"".equals(operatorIdDelete.trim())){
			OperatorResult or = Operator.get(operatorIdDelete, userId, filter, dbResource, true);
			sqlcust = or.getSqls();
		}
		/**索引表字段对象*/
		String treeTableName=filter.getValue(TreeParam.TABLE_NAME);
		TreeIndexFields treeFields=TreeIndexFields.getTreeFields(treeTableName);
		/** 删除索引表中对应的数据 */
		ArrayList<String> sqlIndex = null;
		IndexTable mIndexTable = IndexTable.getNewInstance(userId, 
														   treeTableName);
		sqlIndex = mIndexTable.getDeleteSql(filter.getValue(treeFields.getNodeId())).getSqls();
		if(sqlcust!=null){
			sql.addAll(sqlcust);
		}
		if(sqlIndex!=null){
			sql.addAll(sqlIndex);;
		}
	}
	
	/**
	 * 根据传入的业务对象表数据容器，生成更新业务对象表对应索引表所需数据的映射关系
	 * @param indexFilter 业务对象表数据容器
	 * @throws ErrorMessage 
	 */
	/**
	 * 
	 * @param filter			参数容器
	 * @param type				
	 * @param realId			索引NODE_CODE
	 * @return	DataFilter
	 * @throws ErrorMessage
	 */
	private DataFilter _generatorUpdateIndexFilter(DataFilter filter,String type,String realId) throws ErrorMessage{
		String treeTableName=filter.getValue(TreeParam.TABLE_NAME);
		DataFilter indexFilter=new DataFilter();
		TreeIndexFields treeFields=TreeIndexFields.getTreeFields(treeTableName);
		
		indexFilter.put(treeFields.getNodeParent(), filter.getValue(treeFields.getNodeParent()));
		indexFilter.put(treeFields.getNodeName(), filter.getValue(TreeParam.NAME));
		indexFilter.put(treeFields.getNodeDesc(), filter.getValue(TreeParam.DESC));
		if(realId==null){
			realId = filter.getValue(treeFields.getRealId());
		}
		indexFilter.put(treeFields.getRealId(), realId);
		indexFilter.put(treeFields.getOperatorType(), filter.getValue(TreeParam.OPERATOR_TYPE));
		indexFilter.put(treeFields.getNodeType(),filter.getValue(TreeParam.NODE_TYPE));
		indexFilter.put("table_name", treeTableName);
		indexFilter.put(treeFields.getNodeSequence(), filter.getValue(MdStruc.BmModelThemeStruc.ORID));
		return indexFilter;
	}
}
